using System;
using System.Collections.Generic;
using System.Text;
using ChEngine;
using NUnit.Framework;
using System.CodeDom;
using System.CodeDom.Compiler;
using System.Diagnostics;
using System.Reflection;
using System.Text.RegularExpressions;

namespace TestGen
{
    [TestFixture]
    public class Ox88ChessBoardTests
    {
        [Test]
        public void FenParsingSuite()
        {
            ChessBoard board = new ChessBoard();
            ICollection<PerftTestItem> item = PerftTestSuite.GetAll();
            foreach (PerftTestItem pti in item)
            {
                board.SetBoard(pti.Fen);
                Assert.AreEqual(pti.Fen, board.SavePos());
                Assert.AreEqual(FenMaterialBalance(pti.Fen.Split(' ')[0]),board.WhiteMaterialValue-board.BlackMaterialValue);
            }

        }
        private int FenMaterialBalance(string fenPieces)
        {
            int balance=0;
            Regex r = new Regex("p");
            balance -= r.Matches(fenPieces).Count * ChessBoard.PawnValue;
            r = new Regex("n");
            balance -= r.Matches(fenPieces).Count * ChessBoard.KnightValue;
            r = new Regex("b");
            balance -= r.Matches(fenPieces).Count * ChessBoard.BishopValue;
            r = new Regex("r");
            balance -= r.Matches(fenPieces).Count * ChessBoard.RookValue;
            r = new Regex("q");
            balance -= r.Matches(fenPieces).Count * ChessBoard.QueenValue;
            r = new Regex("k");
            balance -= r.Matches(fenPieces).Count * ChessBoard.KingValue;

            r = new Regex("P");
            balance += r.Matches(fenPieces).Count * ChessBoard.PawnValue;
            r = new Regex("N");
            balance += r.Matches(fenPieces).Count * ChessBoard.KnightValue;
            r = new Regex("B");
            balance += r.Matches(fenPieces).Count * ChessBoard.BishopValue;
            r = new Regex("R");
            balance += r.Matches(fenPieces).Count * ChessBoard.RookValue;
            r = new Regex("Q");
            balance += r.Matches(fenPieces).Count * ChessBoard.QueenValue;
            r = new Regex("K");
            balance += r.Matches(fenPieces).Count * ChessBoard.KingValue;

            return balance;
        }
        [Test]
        public void StandardInit()
        {
            ChessBoard board = new ChessBoard();
            Assert.AreEqual(Cell.Invalid,board.EnPassantIndex,  "Invalid en passant.");
            Assert.AreEqual(CastlingAvail.All,board.CastlingStatus, "Invalid castling status");
            Assert.AreEqual(1,board.MovesCount,  "Wrong moves count");
            Assert.AreEqual(0,board.HalfMovesCount,  "Wrong half moves count");
            Assert.AreEqual("rnbqkbnr/pppppppp/8/8/8/8/PPPPPPPP/RNBQKBNR w KQkq - 0 1",board.SavePos(),  "Invalid fen");
        }
        [Test]
        public void StringToCell()
        {
            string files = "abcdefgh";
            for( int file = 0;file<8;++file )
                for (int rank = 1; rank <= 8; ++rank)
                {
                    string cell = files.Substring(file, 1) + rank.ToString();
                    Assert.AreEqual( (Cell)((rank-1) * 16 + file),ChessBoard.FromLiteralCell(cell),  "Wrong FromLiteralToCell:" + cell);
                }
        }
        [Test]
        public void Index8x8()
        {
            string files = "abcdefgh";
            foreach (FieldInfo field in typeof(Cell).GetFields())
            {
                if (!field.IsSpecialName)
                {
                    Cell x88Value = (Cell)field.GetRawConstantValue();
                    if (x88Value == Cell.Invalid)
                    {
                        Assert.AreEqual(-1, ChessBoard.FromCellTo8x8(x88Value));
                    }
                    else
                    {
                        int idx = ChessBoard.FromCellTo8x8(x88Value);
                        string cell = x88Value.ToString();
                        Assert.AreEqual(int.Parse(cell.Substring(1, 1)) * 8 -8+ files.IndexOf(cell.Substring(0, 1)), idx,"Invalid index 8x8:" + cell);
                    }
                }
            }
        }
        [Test]
        public void FromCellToLiteral()
        {
            string files = "abcdefgh";
            foreach (FieldInfo field in typeof(Cell).GetFields())
            {
                if (!field.IsSpecialName)
                {
                    Cell x88Value = (Cell)field.GetRawConstantValue();
                    string cell = ChessBoard.FromCellToLiteral(x88Value);
                    if (x88Value == Cell.Invalid)
                    {
                        Assert.AreEqual("-", cell, "Invalid cell literal:" + x88Value.ToString());
                    }
                    else
                    {
                        int file = ((int)x88Value & 0xF);
                        int rank = (int)x88Value >> 4;
                        Assert.AreEqual(files.Substring(file, 1) + (rank+1).ToString(), cell);
                    }
                }
            }

        }



    }
    

}
